package com.lxlx.weixinlx.utils;



import com.lxlx.weixinlx.anno.ExcelAtrribute;
import com.lxlx.weixinlx.domain.Student;
import org.apache.poi.ss.usermodel.CellStyle;
import org.apache.poi.xssf.usermodel.XSSFCell;
import org.apache.poi.xssf.usermodel.XSSFRow;
import org.apache.poi.xssf.usermodel.XSSFSheet;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.lang.reflect.Field;
import java.util.List;
import java.util.Map;
import java.util.Objects;

/**
 * @author liuhuan
 * @date 2020
 * @描述 导出
 */
public class ExportExcelUtils<T> {


    /**
     * 通用结合ExcelAtrribute自定义注解
     * 基于模板导出
     * objs 数据集合
     * path 模板路径
     * rowIndex 模板行下标
     *name 导出文件名
     * @param params
     */
    public void exportExcela (Map<String,Object> params) throws IOException, IllegalAccessException {
        List<T> objs = (List<T>) params.get("objs");
        String path = (String) params.get("path");
        String name = (String) params.get("name");
        Integer rowIndex = (Integer) params.get("rowIndex");
        HttpServletResponse response = (HttpServletResponse) params.get("response");
        HttpServletRequest request = (HttpServletRequest) params.get("request");

        //基于模板导出
        XSSFWorkbook workbook = new XSSFWorkbook(Objects.requireNonNull(ExportExcelUtils.class.getClassLoader().getResourceAsStream(path)));
        XSSFSheet sheet = workbook.getSheetAt(0);
        //拿到模板行
        XSSFRow row1 = sheet.getRow(rowIndex);
        CellStyle[] cellStyles = new CellStyle[row1.getLastCellNum()];
        for (int i = 0; i < cellStyles.length; i++) {
            //拿到模板样式
            cellStyles[i]=row1.getCell(i).getCellStyle();
        }

        for (int i = 0; i < objs.size(); i++) {
            XSSFRow row = sheet.createRow(i + rowIndex);
            T t = objs.get(i);
            Class<?> clazz = t.getClass();
            //得到属性
            Field[] fields = clazz.getDeclaredFields();

            for (int j = 0; j < cellStyles.length ; j++) {
                XSSFCell cell = row.createCell(j);
                cell.setCellStyle(cellStyles[j]);
                //找出属性中有ExcelAtrribute注解,并且sort = j;
                for (Field field : fields) {
                    ExcelAtrribute annotation = field.getAnnotation(ExcelAtrribute.class);
                    if (annotation != null){
                        int sort = annotation.sort();
                        if (sort == j){
                            //私有设置为true
                            field.setAccessible(true);
                            cell.setCellValue(field.get(t).toString());
                        }

                    }
                }
            }
        }
        //导出
        excelDown(name,response,request,workbook);
        //
    }

    /**
     * 通用结合ExcelAtrribute自定义注解
     * 普通导出
     * objs 数据集合
     *sheetName sheet名称
     * rowIndex 模板行下标
     *name 导出文件名
     * @param params
     */
    public void exportExcelb (Map<String,Object> params) throws IOException, IllegalAccessException {
        List<T> objs = (List<T>) params.get("objs");
        String name = (String) params.get("name");
        String sheetName = (String) params.get("sheetName");
        String[] titles = (String[]) params.get("titles");
        HttpServletResponse response = (HttpServletResponse) params.get("response");
        HttpServletRequest request = (HttpServletRequest) params.get("request");

        XSSFWorkbook workbook = new XSSFWorkbook();
        XSSFSheet sheet = workbook.createSheet(sheetName);
        //String[] titles = {"id","姓名","生日","性别"};
        XSSFRow row = sheet.createRow(0);
        for (int i = 0; i < titles.length; i++) {
            XSSFCell cell = row.createCell(i);
            cell.setCellValue(titles[i]);
        }

        for (int i = 0; i < objs.size(); i++) {
            row = sheet.createRow(i + 1);
            T t = objs.get(i);
            Class<?> clazz = t.getClass();
            //得到属性
            Field[] fields = clazz.getDeclaredFields();

            for (int j = 0; j < titles.length ; j++) {
                XSSFCell cell = row.createCell(j);
                //找出属性中有ExcelAtrribute注解,并且sort = j;
                for (Field field : fields) {
                    ExcelAtrribute annotation = field.getAnnotation(ExcelAtrribute.class);
                    if (annotation != null){
                        int sort = annotation.sort();
                        if (sort == j){
                            //私有设置为true
                            field.setAccessible(true);
                            cell.setCellValue(field.get(t).toString());
                        }

                    }
                }
            }
        }
        //导出
        excelDown(name,response,request,workbook);
        //
    }

    /**
     * 导出
     * @param name
     * @param response
     * @param request
     * @param workbook
     * @throws IOException
     */
    public void excelDown (String name,HttpServletResponse response,HttpServletRequest request,XSSFWorkbook workbook) throws IOException {
        //文件名
        String fileName = name;
        //浏览器及乱码问题
        String agent = request.getHeader("USER-AGENT").toLowerCase();
        response.setContentType("application/vnd.ms-excel");
        String codedFileName = java.net.URLEncoder.encode(fileName, "UTF-8");
        if (agent.contains("firefox")) {
            response.setCharacterEncoding("utf-8");
            response.setHeader("content-disposition", "attachment;filename=" + new String(fileName.getBytes(), "ISO8859-1") + ".xlsx" );
        } else {
            response.setHeader("content-disposition", "attachment;filename=" + codedFileName + ".xlsx");
        }
        //写出
        workbook.write(response.getOutputStream());
    }

}
